package qx.hyj.petrescue.ws;

import jakarta.websocket.*;
import jakarta.websocket.server.PathParam;
import jakarta.websocket.server.ServerEndpoint;
import org.springframework.beans.BeansException;
import org.springframework.context.ApplicationContext;
import org.springframework.context.ApplicationContextAware;
import org.springframework.stereotype.Component;
import qx.hyj.petrescue.config.GetHttpSession;
import qx.hyj.petrescue.entity.Content;
import qx.hyj.petrescue.entity.Users;
import qx.hyj.petrescue.mapper.ContentMapper;
import qx.hyj.petrescue.mapper.Usermapper;

import java.io.IOException;
import java.time.LocalDateTime;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;

@Component
@ServerEndpoint(value = "/websocket/{sendId}", configurator = GetHttpSession.class)
public class WebSocketServer implements ApplicationContextAware {

    // 静态应用上下文
    private static ApplicationContext applicationContext;

    // 在线用户集合
    private static Map<Integer, WebSocketServer> onlineUsers = new ConcurrentHashMap<>();
    // 会话
    private Session session;
    // 用户名
    private Integer userId;
    // 内容服务
    private Usermapper usermapper;
    private ContentMapper contentMapper;

    @Override
    public void setApplicationContext(ApplicationContext context) throws BeansException {
        applicationContext = context;
    }

    @OnOpen
    public void onOpen(Session session, @PathParam("sendId") Integer userId) {
        // 从应用上下文中获取mapper实例
        this.usermapper = applicationContext.getBean(Usermapper.class);
        this.contentMapper = applicationContext.getBean(ContentMapper.class);

        this.session = session;
        this.userId = userId;
        onlineUsers.put(userId, this);
        Users users = usermapper.selectById(userId);
        broadcastMessage("用户 " + users.getNickname() + " 已上线");
    }

    // 其他方法保持不变...
    @OnMessage
    public void onMessage(String message,
                          @PathParam("sendId") Integer sendId) throws IOException {
        int colonIndex = message.indexOf(':');
        String receiveId= message.substring(0, colonIndex);
        String contentAdd = message.substring(colonIndex + 1);   // 获取冒号后的所有内容
        sendMessageToUser(Integer.parseInt(receiveId), message);
        Content content = new Content().builder()
                .sendId(sendId)
                .receiveId(Integer.parseInt(receiveId))
                .content(contentAdd)
                .isRead(0)
                .createTime(LocalDateTime.now())
                .build();
        contentMapper.insert(content);
    }

    @OnClose
    public void onClose(Session session) {
        onlineUsers.remove(userId);
        // 这里也需要注意，如果用户已下线，可能无法获取nickname
        broadcastMessage("用户 " + userId + " 已下线");

    }

    @OnError
    public void onError(Throwable error) {
        System.out.println("发生错误：" + error.getMessage());
    }

    // 广播消息给所有在线用户
    private void broadcastMessage(String message) {
        onlineUsers.forEach((id, server) -> {
            try {
                if (server.session.isOpen()) {
                    server.session.getBasicRemote().sendText(message);
                }
            } catch (IOException e) {
                e.printStackTrace();
            }
        });
    }

    // 发送消息给指定用户
    private void sendMessageToUser(Integer targetUserId, String message) {
        WebSocketServer server = onlineUsers.get(targetUserId);
        if (server != null && server.session.isOpen()) {
            try {
                server.session.getBasicRemote().sendText(message);
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }

    // 发送消息给当前用户
    private void sendMessage(String message) {
        try {
            if (session.isOpen()) {
                session.getBasicRemote().sendText(message);
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}